// PWA工具类 - 管理Service Worker和离线功能

/**
 * PWA管理器类
 */
export class PWAManager {
  constructor() {
    this.registration = null
    this.isOnline = navigator.onLine
    this.updateAvailable = false
    this.callbacks = {
      onOnlineStatusChange: [],
      onUpdateAvailable: [],
      onUpdateInstalled: []
    }
    
    this.init()
  }

  /**
   * 初始化PWA功能
   */
  async init() {
    // 监听在线状态变化
    this.setupOnlineStatusListener()
    
    // 注册Service Worker
    if ('serviceWorker' in navigator) {
      try {
        await this.registerServiceWorker()
        console.log('PWA initialized successfully')
      } catch (error) {
        console.error('PWA initialization failed:', error)
      }
    } else {
      console.warn('Service Worker not supported')
    }
  }

  /**
   * 注册Service Worker
   */
  async registerServiceWorker() {
    try {
      this.registration = await navigator.serviceWorker.register('/sw.js', {
        scope: '/'
      })
      
      console.log('Service Worker registered:', this.registration)
      
      // 监听Service Worker更新
      this.registration.addEventListener('updatefound', () => {
        this.handleServiceWorkerUpdate()
      })
      
      // 检查是否有等待中的Service Worker
      if (this.registration.waiting) {
        this.showUpdateAvailable()
      }
      
      // 监听控制器变化
      navigator.serviceWorker.addEventListener('controllerchange', () => {
        this.handleControllerChange()
      })
      
      return this.registration
    } catch (error) {
      console.error('Service Worker registration failed:', error)
      throw error
    }
  }

  /**
   * 处理Service Worker更新
   */
  handleServiceWorkerUpdate() {
    const newWorker = this.registration.installing
    
    newWorker.addEventListener('statechange', () => {
      if (newWorker.state === 'installed') {
        if (navigator.serviceWorker.controller) {
          // 有新版本可用
          this.showUpdateAvailable()
        } else {
          // 首次安装
          this.notifyCallbacks('onUpdateInstalled')
        }
      }
    })
  }

  /**
   * 显示更新可用提示
   */
  showUpdateAvailable() {
    this.updateAvailable = true
    this.notifyCallbacks('onUpdateAvailable')
  }

  /**
   * 处理控制器变化
   */
  handleControllerChange() {
    try {
      // 页面被新的Service Worker控制，但不要立即刷新
      // 只在用户确认的情况下才刷新
      console.log('Service Worker controller changed')
      this.notifyCallbacks('onControllerChange')
      
      // 移除自动刷新，避免干扰用户操作
      // window.location.reload()
    } catch (error) {
      console.error('Error handling controller change:', error)
    }
  }

  /**
   * 应用更新
   */
  async applyUpdate() {
    if (!this.registration || !this.registration.waiting) {
      return false
    }
    
    // 告诉等待中的Service Worker跳过等待
    this.registration.waiting.postMessage({ type: 'SKIP_WAITING' })
    return true
  }

  /**
   * 设置在线状态监听器
   */
  setupOnlineStatusListener() {
    const handleOnline = () => {
      this.isOnline = true
      this.notifyCallbacks('onOnlineStatusChange', true)
    }
    
    const handleOffline = () => {
      this.isOnline = false
      this.notifyCallbacks('onOnlineStatusChange', false)
    }
    
    window.addEventListener('online', handleOnline)
    window.addEventListener('offline', handleOffline)
  }

  /**
   * 添加事件回调
   */
  on(event, callback) {
    if (this.callbacks[event]) {
      this.callbacks[event].push(callback)
    }
  }

  /**
   * 移除事件回调
   */
  off(event, callback) {
    if (this.callbacks[event]) {
      const index = this.callbacks[event].indexOf(callback)
      if (index > -1) {
        this.callbacks[event].splice(index, 1)
      }
    }
  }

  /**
   * 通知回调函数
   */
  notifyCallbacks(event, data) {
    if (this.callbacks[event]) {
      this.callbacks[event].forEach(callback => {
        try {
          callback(data)
        } catch (error) {
          console.error(`Error in ${event} callback:`, error)
        }
      })
    }
  }

  /**
   * 获取缓存使用情况
   */
  async getCacheUsage() {
    if ('storage' in navigator && 'estimate' in navigator.storage) {
      try {
        const estimate = await navigator.storage.estimate()
        return {
          used: estimate.usage,
          available: estimate.quota,
          percentage: Math.round((estimate.usage / estimate.quota) * 100)
        }
      } catch (error) {
        console.error('Failed to get cache usage:', error)
        return null
      }
    }
    return null
  }

  /**
   * 清理缓存
   */
  async clearCache() {
    try {
      const cacheNames = await caches.keys()
      await Promise.all(
        cacheNames.map(cacheName => caches.delete(cacheName))
      )
      console.log('All caches cleared')
      return true
    } catch (error) {
      console.error('Failed to clear cache:', error)
      return false
    }
  }

  /**
   * 预缓存资源
   */
  async precacheResources(urls) {
    if (!this.registration) {
      console.warn('Service Worker not registered')
      return false
    }
    
    try {
      const cache = await caches.open('xiaozhi-precache')
      await cache.addAll(urls)
      console.log('Resources precached successfully')
      return true
    } catch (error) {
      console.error('Failed to precache resources:', error)
      return false
    }
  }

  /**
   * 检查网络连接质量
   */
  getConnectionInfo() {
    if ('connection' in navigator) {
      const connection = navigator.connection
      return {
        effectiveType: connection.effectiveType,
        downlink: connection.downlink,
        rtt: connection.rtt,
        saveData: connection.saveData
      }
    }
    return null
  }

  /**
   * 获取安装提示
   */
  getInstallPrompt() {
    return this.installPrompt
  }

  /**
   * 设置安装提示
   */
  setInstallPrompt(prompt) {
    this.installPrompt = prompt
  }

  /**
   * 显示安装提示
   */
  async showInstallPrompt() {
    if (!this.installPrompt) {
      return false
    }
    
    try {
      const result = await this.installPrompt.prompt()
      console.log('Install prompt result:', result)
      this.installPrompt = null
      return result.outcome === 'accepted'
    } catch (error) {
      console.error('Install prompt failed:', error)
      return false
    }
  }
}

// 创建全局PWA管理器实例
export const pwaManager = new PWAManager()

/**
 * 离线存储管理器
 */
export class OfflineStorageManager {
  constructor() {
    this.dbName = 'XiaozhiMedicalDB'
    this.dbVersion = 1
    this.db = null
  }

  /**
   * 初始化IndexedDB
   */
  async init() {
    return new Promise((resolve, reject) => {
      const request = indexedDB.open(this.dbName, this.dbVersion)
      
      request.onerror = () => reject(request.error)
      request.onsuccess = () => {
        this.db = request.result
        resolve(this.db)
      }
      
      request.onupgradeneeded = (event) => {
        const db = event.target.result
        
        // 创建对象存储
        if (!db.objectStoreNames.contains('offlineData')) {
          const store = db.createObjectStore('offlineData', { keyPath: 'id', autoIncrement: true })
          store.createIndex('type', 'type', { unique: false })
          store.createIndex('timestamp', 'timestamp', { unique: false })
        }
        
        if (!db.objectStoreNames.contains('userActions')) {
          const store = db.createObjectStore('userActions', { keyPath: 'id', autoIncrement: true })
          store.createIndex('action', 'action', { unique: false })
          store.createIndex('timestamp', 'timestamp', { unique: false })
        }
      }
    })
  }

  /**
   * 存储离线数据
   */
  async storeOfflineData(type, data) {
    if (!this.db) await this.init()
    
    return new Promise((resolve, reject) => {
      const transaction = this.db.transaction(['offlineData'], 'readwrite')
      const store = transaction.objectStore('offlineData')
      
      const request = store.add({
        type,
        data,
        timestamp: Date.now()
      })
      
      request.onsuccess = () => resolve(request.result)
      request.onerror = () => reject(request.error)
    })
  }

  /**
   * 获取离线数据
   */
  async getOfflineData(type) {
    if (!this.db) await this.init()
    
    return new Promise((resolve, reject) => {
      const transaction = this.db.transaction(['offlineData'], 'readonly')
      const store = transaction.objectStore('offlineData')
      const index = store.index('type')
      
      const request = index.getAll(type)
      
      request.onsuccess = () => resolve(request.result)
      request.onerror = () => reject(request.error)
    })
  }

  /**
   * 删除离线数据
   */
  async deleteOfflineData(id) {
    if (!this.db) await this.init()
    
    return new Promise((resolve, reject) => {
      const transaction = this.db.transaction(['offlineData'], 'readwrite')
      const store = transaction.objectStore('offlineData')
      
      const request = store.delete(id)
      
      request.onsuccess = () => resolve()
      request.onerror = () => reject(request.error)
    })
  }

  /**
   * 存储用户操作
   */
  async storeUserAction(action, data) {
    if (!this.db) await this.init()
    
    return new Promise((resolve, reject) => {
      const transaction = this.db.transaction(['userActions'], 'readwrite')
      const store = transaction.objectStore('userActions')
      
      const request = store.add({
        action,
        data,
        timestamp: Date.now(),
        synced: false
      })
      
      request.onsuccess = () => resolve(request.result)
      request.onerror = () => reject(request.error)
    })
  }

  /**
   * 获取未同步的用户操作
   */
  async getUnsyncedActions() {
    if (!this.db) await this.init()
    
    return new Promise((resolve, reject) => {
      const transaction = this.db.transaction(['userActions'], 'readonly')
      const store = transaction.objectStore('userActions')
      
      const request = store.getAll()
      
      request.onsuccess = () => {
        const actions = request.result.filter(action => !action.synced)
        resolve(actions)
      }
      request.onerror = () => reject(request.error)
    })
  }

  /**
   * 标记操作为已同步
   */
  async markActionSynced(id) {
    if (!this.db) await this.init()
    
    return new Promise((resolve, reject) => {
      const transaction = this.db.transaction(['userActions'], 'readwrite')
      const store = transaction.objectStore('userActions')
      
      const getRequest = store.get(id)
      
      getRequest.onsuccess = () => {
        const action = getRequest.result
        if (action) {
          action.synced = true
          const putRequest = store.put(action)
          putRequest.onsuccess = () => resolve()
          putRequest.onerror = () => reject(putRequest.error)
        } else {
          resolve()
        }
      }
      getRequest.onerror = () => reject(getRequest.error)
    })
  }
}

// 创建全局离线存储管理器实例
export const offlineStorage = new OfflineStorageManager()

/**
 * PWA工具函数
 */
export const PWAUtils = {
  /**
   * 检查是否为PWA环境
   */
  isPWA() {
    return window.matchMedia('(display-mode: standalone)').matches ||
           window.navigator.standalone === true
  },

  /**
   * 检查是否支持PWA
   */
  isPWASupported() {
    return 'serviceWorker' in navigator && 'PushManager' in window
  },

  /**
   * 检查是否为移动设备
   */
  isMobile() {
    return /Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test(navigator.userAgent)
  },

  /**
   * 获取设备信息
   */
  getDeviceInfo() {
    return {
      userAgent: navigator.userAgent,
      platform: navigator.platform,
      language: navigator.language,
      cookieEnabled: navigator.cookieEnabled,
      onLine: navigator.onLine,
      hardwareConcurrency: navigator.hardwareConcurrency,
      deviceMemory: navigator.deviceMemory || 'unknown'
    }
  },

  /**
   * 请求通知权限
   */
  async requestNotificationPermission() {
    if (!('Notification' in window)) {
      console.warn('This browser does not support notifications')
      return false
    }
    
    if (Notification.permission === 'granted') {
      return true
    }
    
    if (Notification.permission === 'denied') {
      return false
    }
    
    const permission = await Notification.requestPermission()
    return permission === 'granted'
  },

  /**
   * 显示通知
   */
  showNotification(title, options = {}) {
    if (Notification.permission === 'granted') {
      return new Notification(title, {
        icon: '/favicon.ico',
        badge: '/favicon.ico',
        ...options
      })
    }
    return null
  },

  /**
   * 添加到主屏幕提示
   */
  canInstall() {
    return pwaManager.getInstallPrompt() !== null
  },

  /**
   * 检查PWA是否已安装
   */
  isInstalled() {
    return this.isPWA()
  },

  /**
   * 安装PWA
   */
  async install() {
    return await pwaManager.showInstallPrompt()
  },

  /**
   * 提示安装PWA
   */
  async promptInstall() {
    return await pwaManager.showInstallPrompt()
  }
}